# coding=utf-8
import random
import shlex
import subprocess
import time
import os

import lorun


def judge(language, codes, data_in_d, data_out_d, num, time_limit, memory_limit):
    write_file(language, codes)
    ans = {}
    if language in ["java", 'python2', 'python3']:
        time_limit = time_limit * 2
        memory_limit = memory_limit * 2
    for i in range(1, num + 1):
        # data_in_d[str(i)] = json.load(data_in_d[str(i)])
        # data_out_d[str(i)] = json.load(data_out_d[str(i)])
        ans_once = judge_once(language, data_in_d[str(i)], data_out_d[str(i)], time_limit, memory_limit)
        # print ans_once
        ans[str(i)] = ans_once
        time.sleep(0.2)
        temp_out_data = file("../work_dir/data.out", "w")
        temp_out_data.close()
    return ans


def write_file(language, codes):
    if language == "gcc":
        file_code = open("../work_dir/gcc/main.c", mode="w")
        file_code.write(codes)
        file_code.close()
    elif language == "cpp":
        file_code = open("../work_dir/cpp/main.cpp", mode="w")
        file_code.write(codes)
        file_code.close()
    elif language == "java":
        file_code = open("../work_dir/java/Main.java", mode="w")
        file_code.write(codes)
        file_code.close()
    elif language == "python2":
        file_code = open("../work_dir/python2/main.py", mode="w")
        file_code.write(codes)
        file_code.close()
    elif language == "python3":
        file_code = open("../work_dir/python3/main.py", mode="w")
        file_code.write(codes)
        file_code.close()
    return


def code_compile(language):
    ans = os.path.abspath(__file__).split('/')[:-2]
    path = ""
    for item in ans:
        path += item
        path += '/'
    path = path[:-1]
    build_cmd = {
        "gcc": "gcc " + path + "/work_dir/gcc/main.c -o " + path + "/work_dir/gcc/main -Wall -lm -O2 -std=c99 --static -DONLINE_JUDGE",
        "cpp": "g++ " + path + "/work_dir/cpp/main.cpp -O2 -Wall -lm --static -DONLINE_JUDGE -o " + path + "/work_dir/cpp/main",
        "java": "javac " + path + "/work_dir/java/Main.java",
        "python2": "python2 -m py_compile " + path + "/work_dir/python2/main.py",
        "python3": "python3 -m py_compile " + path + "/work_dir/python3/main.py"
    }
    dir_work = path + "/work_dir/" + language
    p = subprocess.Popen(
        build_cmd[language],
        shell=True,
        cwd=dir_work,
        stdout=subprocess.PIPE,
        stderr=subprocess.PIPE)
    # 获取编译错误信息
    out, err = p.communicate()
    f = file("../work_dir/error.txt", 'w')
    f.write(err)
    f.write(out)
    f.close()
    # 返回值为0,编译成功
    if p.returncode == 0:
        return True
    return False


def judge_run(language, time_limit, memory_limit):
    ans = os.path.abspath(__file__).split('/')[:-2]
    path = ""
    for item in ans:
        path += item
        path += '/'
    path = path[:-1]
    run_cmd = {
        "java": "java -cp " + path + "/work_dir/java Main",
        "python2": "python2 " + path + "/work_dir/python2/main.pyc",
        "python3": "python3 " + path + "/work_dir/python3/__pycache__/main.cpython-310.pyc",
        "gcc": path + "/work_dir/gcc/main",
        "cpp": path + "/work_dir/cpp/main"
    }
    main_exe = shlex.split(run_cmd[language])
    input_data = file("../work_dir/in.txt")
    temp_out_data = file("../work_dir/data.out", "w")
    run_conf = {
        'args': main_exe,
        'fd_in': input_data.fileno(),
        'fd_out': temp_out_data.fileno(),
        'timelimit': time_limit,  # MS
        'memorylimit': memory_limit,  # KB
    }
    # print (run_conf)
    res = lorun.run(run_conf)
    input_data.close()
    temp_out_data.close()
    return res


def judge_once(language, data_in, data_out, time_limit, memory_limit):
    file_in = open("../work_dir/in.txt", mode="w")
    file_in.write(data_in)
    file_in.close()
    b = code_compile(language)
    if not b:
        return {"key": "CE"}
    res = judge_run(language, time_limit, memory_limit)
    # print (res)
    if res['result'] == 5:
        return {"key": "RE"}
    elif res['result'] == 2:
        return {"key": "TLE"}
    elif res['result'] == 3:
        return {"key": "MLE"}
    # 删除\r,删除行末的空格和换行
    data_compare = file("../work_dir/data.out").read().replace('\r', '').rstrip()
    # 除去空格,tab,换行相同
    if data_compare == data_out:
        tu = str(random.randint(5, 10)) if int(str(res['timeused']).replace('L', '')) < 5 else int(
            str(res['timeused']).replace('L', ''))
        return {"key": "AC", "run_time": tu, "memory_use": str(res['memoryused']).replace('L', '')}
    elif data_compare.split() == data_out.split():
        return {"key": "PE"}
    # 输出多了
    elif (data_compare in data_out) and (data_compare != ""):
        return {"key": "OLE"}
    return {"key": "WA"}
